from PyQt6.QtWidgets import (QVBoxLayout, QHBoxLayout, QLabel, 
                           QPushButton, QLineEdit, QTextEdit, QProgressBar,
                           QFrame, QScrollArea, QWidget, QMessageBox, QStackedWidget, QGridLayout, QSlider, QFileDialog, QSizePolicy, QDialog)
from PyQt6.QtCore import Qt, pyqtSignal, QSize, QThread, QTimer
from PyQt6.QtGui import QIcon, QPixmap
from .base_page import BasePage, ContentCard
from ..widgets.reader_widget import ReaderWidget
from ..widgets import BookshelfWidget
from ..widgets.book_card import BookCard
import os
import json
import time
from pathlib import Path
import requests
import re
from bs4 import BeautifulSoup
from urllib.parse import urljoin
import warnings

# 在程序启动时添加以下代码来屏蔽这些警告
warnings.filterwarnings("ignore", category=UserWarning, module="libpng")

class NovelCard(QFrame):
    def __init__(self, title, author="", cover_url="", parent=None):
        super().__init__(parent)
        self.setObjectName("novelCard")
        self.setFixedHeight(120)
        
        layout = QHBoxLayout(self)
        layout.setContentsMargins(15, 15, 15, 15)
        
        # 封面图
        cover = QLabel()
        cover.setFixedSize(64, 90)
        cover.setStyleSheet("""
            background-color: #404040;
            border-radius: 4px;
        """)
        layout.addWidget(cover)
        
        # 信息区域
        info_layout = QVBoxLayout()
        info_layout.setSpacing(4)
        
        title_label = QLabel(title)
        title_label.setStyleSheet("font-size: 16px; font-weight: bold;")
        
        author_label = QLabel(author)
        author_label.setStyleSheet("color: rgba(255, 255, 255, 0.6);")
        
        info_layout.addWidget(title_label)
        info_layout.addWidget(author_label)
        info_layout.addStretch()
        
        layout.addLayout(info_layout)
        layout.addStretch()
        
        # 下载按钮
        download_btn = QPushButton("下载")
        download_btn.setFixedSize(80, 32)
        download_btn.setStyleSheet("""
            QPushButton {
                background-color: #0C61F2;
                border-radius: 4px;
                color: white;
                font-weight: bold;
            }
            QPushButton:hover {
                background-color: #1E74F4;
            }
            QPushButton:pressed {
                background-color: #0A4BC2;
            }
        """)
        layout.addWidget(download_btn)

class NovelDownloader(QWidget):
    def __init__(self, parent=None):
        super().__init__(parent)
        self.init_ui()
        
    def init_ui(self):
        layout = QVBoxLayout(self)
        layout.setContentsMargins(0, 0, 0, 0)
        layout.setSpacing(10)
        
        # 搜索区域
        search_layout = QHBoxLayout()
        
        self.search_input = QLineEdit()
        self.search_input.setPlaceholderText("输入小说名称或链接")
        self.search_input.setFixedHeight(36)
        
        search_btn = QPushButton("搜索")
        search_btn.setFixedSize(80, 36)
        search_btn.clicked.connect(self.search_novel)
        
        search_layout.addWidget(self.search_input)
        search_layout.addWidget(search_btn)
        
        layout.addLayout(search_layout)
        
        # 结果列表区域
        scroll = QScrollArea()
        scroll.setWidgetResizable(True)
        scroll.setHorizontalScrollBarPolicy(Qt.ScrollBarPolicy.ScrollBarAlwaysOff)
        
        scroll_content = QWidget()
        self.results_layout = QVBoxLayout(scroll_content)
        self.results_layout.setSpacing(10)
        self.results_layout.addStretch()
        
        scroll.setWidget(scroll_content)
        layout.addWidget(scroll)
        
        # 下载进度
        progress_group = QFrame()
        progress_group.setObjectName("progressGroup")
        progress_layout = QVBoxLayout(progress_group)
        
        progress_header = QHBoxLayout()
        progress_title = QLabel("下载队列")
        progress_title.setStyleSheet("font-weight: bold;")
        clear_btn = QPushButton("清空")
        clear_btn.clicked.connect(self.clear_progress)
        
        progress_header.addWidget(progress_title)
        progress_header.addStretch()
        progress_header.addWidget(clear_btn)
        
        self.progress_layout = QVBoxLayout()
        self.progress_layout.setSpacing(8)
        
        progress_layout.addLayout(progress_header)
        progress_layout.addLayout(self.progress_layout)
        
        layout.addWidget(progress_group)
    
    def search_novel(self):
        keyword = self.search_input.text().strip()
        if not keyword:
            QMessageBox.warning(self, "提示", "请输入搜索关键词")
            return
            
        # 清空之前的结果
        while self.results_layout.count() > 1:  # 保留最后的stretch
            item = self.results_layout.takeAt(0)
            if item.widget():
                item.widget().deleteLater()
        
        # 这里添加实际的搜索逻辑
        # 示例数据
        results = [
            {"title": "三体", "author": "刘慈欣"},
            {"title": "球状闪电", "author": "刘慈欣"},
            # ... 更多搜索结果
        ]
        
        # 显示结果
        for novel in results:
            card = NovelCard(novel["title"], novel["author"])
            self.results_layout.insertWidget(self.results_layout.count()-1, card)
    
    def add_download_progress(self, title):
        progress_item = QWidget()
        item_layout = QHBoxLayout(progress_item)
        item_layout.setContentsMargins(0, 0, 0, 0)
        
        name_label = QLabel(title)
        progress_bar = QProgressBar()
        progress_bar.setFixedWidth(200)
        progress_bar.setTextVisible(True)
        
        item_layout.addWidget(name_label)
        item_layout.addStretch()
        item_layout.addWidget(progress_bar)
        
        self.progress_layout.addWidget(progress_item)
        return progress_bar
    
    def clear_progress(self):
        while self.progress_layout.count():
            item = self.progress_layout.takeAt(0)
            if item.widget():
                item.widget().deleteLater()

class BookCard(QFrame):
    doubleClicked = pyqtSignal(str)  # 发送书籍ID信号
    deleteClicked = pyqtSignal(str)  # 添加删除信号
    
    def __init__(self, book_data, size=150, parent=None):
        super().__init__(parent)
        self.book_data = book_data
        self.size = size
        self.init_ui()
        
    def init_ui(self):
        self.setFixedSize(self.size, int(self.size * 1.4))
        self.setObjectName("bookCard")
        
        layout = QVBoxLayout(self)
        layout.setContentsMargins(8, 8, 8, 8)
        layout.setSpacing(4)
        
        # 顶部信息栏
        top_bar = QHBoxLayout()
        top_bar.setContentsMargins(0, 0, 0, 0)
        top_bar.setSpacing(4)
        
        # 进度标签
        progress = self.book_data.get('progress', 0)
        progress_label = QLabel(f"{progress}%" if progress > 0 else "未阅读")
        progress_label.setObjectName("progressLabel")
        progress_label.setAlignment(Qt.AlignmentFlag.AlignLeft | Qt.AlignmentFlag.AlignTop)
        top_bar.addWidget(progress_label)
        
        # 添加弹性空间
        top_bar.addStretch()
        
        # 删除按钮
        delete_btn = QPushButton("×")
        delete_btn.setObjectName("deleteButton")
        delete_btn.setFixedSize(16, 16)
        delete_btn.clicked.connect(lambda: self.deleteClicked.emit(self.book_data['id']))
        delete_btn.setCursor(Qt.CursorShape.PointingHandCursor)
        top_bar.addWidget(delete_btn)
        
        layout.addLayout(top_bar)
        
        # 封面图片
        cover_label = QLabel()
        if self.book_data.get('cover'):
            pixmap = QPixmap(self.book_data['cover'])
        else:
            pixmap = QPixmap("resources/icons/book.svg")
        pixmap = pixmap.scaled(self.size-16, int(self.size*0.8), 
                             Qt.AspectRatioMode.KeepAspectRatio,
                             Qt.TransformationMode.SmoothTransformation)
        cover_label.setPixmap(pixmap)
        cover_label.setAlignment(Qt.AlignmentFlag.AlignCenter)
        layout.addWidget(cover_label)
        
        # 书名
        title_label = QLabel(self.book_data['title'])
        title_label.setWordWrap(True)
        title_label.setAlignment(Qt.AlignmentFlag.AlignCenter)
        title_label.setStyleSheet("font-size: 12px;")
        layout.addWidget(title_label)
        
        self.setStyleSheet("""
            QFrame#bookCard {
                background-color: rgba(255, 255, 255, 0.05);
                border-radius: 8px;
            }
            QFrame#bookCard:hover {
                background-color: rgba(255, 255, 255, 0.1);
            }
            QLabel#progressLabel {
                color: #0C61F2;
                font-size: 10px;
                font-weight: bold;
            }
            QPushButton#deleteButton {
                background: transparent;
                border: none;
                color: rgba(255, 255, 255, 0.5);
                font-size: 14px;
                font-weight: bold;
            }
            QPushButton#deleteButton:hover {
                color: #FF4444;
            }
        """)
        
    def mouseDoubleClickEvent(self, event):
        self.doubleClicked.emit(self.book_data['id'])
        super().mouseDoubleClickEvent(event)
        
    def update_size(self, size):
        self.size = size
        self.setFixedSize(size, int(size * 1.4))
        # 更新封面图片大小
        if self.layout().itemAt(1):
            cover_label = self.layout().itemAt(1).widget()
            if self.book_data.get('cover'):
                pixmap = QPixmap(self.book_data['cover'])
            else:
                pixmap = QPixmap("resources/icons/book.svg")
            pixmap = pixmap.scaled(size-16, int(size*0.8), 
                                 Qt.AspectRatioMode.KeepAspectRatio,
                                 Qt.TransformationMode.SmoothTransformation)
            cover_label.setPixmap(pixmap)

class NovelPage(BasePage):
    def __init__(self):
        super().__init__()
        self.set_title("我的书架")
        self.init_ui()
        # 初始化后加载书架
        QTimer.singleShot(100, self.load_books)

    def init_ui(self):
        # 创建堆叠窗口
        self.stack = QStackedWidget()
        
        # 创建书架页面容器
        bookshelf_container = QWidget()
        bookshelf_layout = QVBoxLayout(bookshelf_container)
        bookshelf_layout.setContentsMargins(0, 0, 0, 0)
        bookshelf_layout.setSpacing(0)
        
        # 创建书架页面
        self.bookshelf = BookshelfWidget()
        self.bookshelf.bookSelected.connect(self.open_reader)
        bookshelf_layout.addWidget(self.bookshelf)
        
        # 创建阅读器页面
        self.reader = ReaderWidget()
        self.reader.backClicked.connect(self.show_bookshelf)
        self.reader.progressUpdated.connect(self.on_progress_updated)
        
        # 添加页面到堆叠窗口
        self.stack.addWidget(bookshelf_container)
        self.stack.addWidget(self.reader)
        
        self.main_layout.addWidget(self.stack)
    
    def load_books(self):
        """加载并排序书架中的书籍"""
        try:
            if hasattr(self, 'bookshelf'):
                self.bookshelf.load_books()  # 这个方法内部会处理排序和刷新
        except Exception as e:
            print(f"加载书架失败: {str(e)}")
    
    def show_reader(self):
        """显示阅读器"""
        self.stack.setCurrentWidget(self.reader)

    def show_bookshelf(self):
        """显示书架并刷新"""
        self.stack.setCurrentWidget(self.stack.widget(0))
        # 返回书架时刷新显示
        self.bookshelf.sort_and_refresh()

    def on_progress_updated(self, book_data):
        """处理进度更新"""
        try:
            # 更新书架数据
            for book in self.bookshelf.books:
                if book['id'] == book_data['id']:
                    book['progress'] = book_data['progress']
                    book['last_position'] = book_data['last_position']
                    break
            
            # 保存更新后的数据
            self.bookshelf.save_books()
            
        except Exception as e:
            print(f"更新进度失败: {str(e)}")

    def open_reader(self, book_id):
        """打开阅读器时更新操作信息"""
        try:
            current_time = int(time.time())
            print(f"\n打开书籍 {book_id}, 更新时间戳: {current_time}")
            
            # 查找选中的书籍数据并打开阅读器
            book = next((b for b in self.bookshelf.books if b['id'] == book_id), None)
            if book:
                # 更新书籍时间戳和操作信息
                self.bookshelf.update_book_time(book_id, current_time, "打开阅读")
                
                # 打开阅读器
                self.reader.load_book(book)
                self.show_reader()
                
                print(f"书籍打开完成: {book['title']}\n")
                
        except Exception as e:
            print(f"打开阅读器失败: {str(e)}")

    def update_bookshelf(self):
        """更新书架显示"""
        if hasattr(self, 'bookshelf'):
            self.bookshelf.sort_and_refresh()

    def import_book(self, book_info):
        """导入新书到书架"""
        try:
            # 设置新书的基本信息
            current_time = int(time.time())
            book_info['last_read_time'] = current_time
            book_info['last_operation'] = "新增书籍"
            book_info['add_time'] = time.strftime('%Y-%m-%d %H:%M:%S')
            book_info['id'] = str(current_time)
            book_info['progress'] = 0
            
            # 添加新书
            if self.bookshelf.add_new_book(book_info):
                print(f"新书导入成功: {book_info['title']}, 时间戳: {current_time}")
                return True
            
        except Exception as e:
            print(f"导入书籍失败: {str(e)}")
            return False

class AddNetBookDialog(QDialog):
    """添加网络书籍对话框"""
    def __init__(self, parent=None):
        super().__init__(parent)
        self.setWindowTitle("添加网络书籍")
        self.setFixedSize(500, 150)
        
        layout = QVBoxLayout(self)
        
        # URL输入区域
        url_layout = QHBoxLayout()
        url_label = QLabel("书籍网址:")
        self.url_input = QLineEdit()
        self.url_input.setPlaceholderText("请输入书籍链接")
        url_layout.addWidget(url_label)
        url_layout.addWidget(self.url_input)
        layout.addLayout(url_layout)
        
        # 进度条
        self.progress_bar = QProgressBar()
        self.progress_bar.hide()
        layout.addWidget(self.progress_bar)
        
        # 按钮区域
        btn_layout = QHBoxLayout()
        self.download_btn = QPushButton("下载")
        self.download_btn.clicked.connect(self.start_download)
        cancel_btn = QPushButton("取消")
        cancel_btn.clicked.connect(self.reject)
        btn_layout.addWidget(self.download_btn)
        btn_layout.addWidget(cancel_btn)
        layout.addLayout(btn_layout)
        
        self.downloader = None

    def start_download(self):
        url = self.url_input.text().strip()
        if not url:
            QMessageBox.warning(self, "错误", "请输入书籍链接")
            return
            
        self.download_btn.setEnabled(False)
        self.progress_bar.show()
        self.progress_bar.setRange(0, 0)  # 显示忙碌状态
        
        self.downloader = BookDownloader(url)
        self.downloader.progress_updated.connect(self.update_progress)
        self.downloader.download_finished.connect(self.download_finished)
        self.downloader.error_occurred.connect(self.download_error)
        self.downloader.start()

    def update_progress(self, current, total):
        self.progress_bar.setRange(0, total)
        self.progress_bar.setValue(current)

    def download_finished(self, book_info):
        self.progress_bar.hide()
        self.download_btn.setEnabled(True)
        QMessageBox.information(self, "成功", "书籍下载完成！")
        self.accept()

    def download_error(self, error_msg):
        self.progress_bar.hide()
        self.download_btn.setEnabled(True)
        QMessageBox.warning(self, "错误", f"下载失败: {error_msg}")

class BookDownloader(QThread):
    progress_updated = pyqtSignal(int, int)
    download_finished = pyqtSignal(dict)
    error_occurred = pyqtSignal(str)

    # 更新支持的网站配置为免费合法的资源
    SUPPORTED_SITES = {
        'aixdzs': {  # 爱下电子书
            'domain': ['www.aixdzs.com'],
            'selectors': {
                'title': '.book-title h1',
                'author': '.book-title span.red',
                'chapter_list': '.chapter-list a',
                'content': '#content'
            }
        },
        'shuyuzhe': {  # 书语者
            'domain': ['www.shuyuzhe.com'],
            'selectors': {
                'title': '.book-info h1',
                'author': '.book-info .author',
                'chapter_list': '.chapter-list a',
                'content': '.content'
            }
        },
        'mfxsydw': {  # 免费小说阅读网
            'domain': ['www.mfxsydw.com'],
            'selectors': {
                'title': '.book-info h1',
                'author': '.book-info .author',
                'chapter_list': '.chapter-list a',
                'content': '.content'
            }
        },
        'wanbentxt': {  # 完本神站
            'domain': ['www.wanbentxt.com'],
            'selectors': {
                'title': '.book-title',
                'author': '.book-author',
                'chapter_list': '.chapter-list a',
                'content': '.content'
            }
        }
    }

    def __init__(self, url):
        super().__init__()
        self.url = url
        self.headers = {
            'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36'
        }
        self.session = requests.Session()
        self.session.headers.update(self.headers)
        self.retry_count = 3
        self.delay = 1  # 降低延迟时间

    def get_site_config(self, url):
        """根据URL识别网站并返回对应的配置"""
        from urllib.parse import urlparse
        domain = urlparse(url).netloc
        
        for site, config in self.SUPPORTED_SITES.items():
            if domain in config['domain']:
                return site, config['selectors']
        
        raise ValueError(f"不支持的网站: {domain}")

    def download_with_retry(self, url):
        for i in range(self.retry_count):
            try:
                response = self.session.get(url)
                response.raise_for_status()
                return response
            except requests.exceptions.RequestException as e:
                print(f"请求失败，重试 {i+1}/{self.retry_count}: {str(e)}")
                time.sleep(self.delay)
        raise Exception("所有重试失败")

    def run(self):
        try:
            site_name, selectors = self.get_site_config(self.url)
            print(f"正在下载来自 {site_name} 的书籍...")

            # 获取书籍信息页面
            response = self.download_with_retry(self.url)
            soup = BeautifulSoup(response.text, 'html.parser')

            # 解析书籍基本信息
            title = soup.select_one(selectors['title']).text.strip()
            author = soup.select_one(selectors['author']).text.strip()
            
            # 获取章节列表
            chapters = []
            chapter_links = soup.select(selectors['chapter_list'])
            total_chapters = len(chapter_links)
            
            # 创建下载目录
            save_dir = Path("downloads") / title
            save_dir.mkdir(parents=True, exist_ok=True)
            
            for i, link in enumerate(chapter_links):
                try:
                    chapter_url = link['href']
                    if not chapter_url.startswith('http'):
                        chapter_url = urljoin(self.url, chapter_url)
                    chapter_title = link.text.strip()
                    
                    # 检查是否已下载
                    chapter_file = save_dir / f"{i+1:04d}_{chapter_title}.txt"
                    if chapter_file.exists():
                        with open(chapter_file, 'r', encoding='utf-8') as f:
                            content = f.read()
                    else:
                        # 获取章节内容
                        chapter_response = self.download_with_retry(chapter_url)
                        chapter_soup = BeautifulSoup(chapter_response.text, 'html.parser')
                        content = chapter_soup.select_one(selectors['content']).text.strip()
                        
                        # 保存章节
                        with open(chapter_file, 'w', encoding='utf-8') as f:
                            f.write(content)
                        
                        # 下载延迟
                        time.sleep(self.delay)
                    
                    chapters.append({
                        'title': chapter_title,
                        'content': content
                    })
                    
                    self.progress_updated.emit(i + 1, total_chapters)
                    
                except Exception as e:
                    print(f"下载章节 {chapter_title} 失败: {str(e)}")
                    continue

            # 合并保存
            save_path = save_dir / f"{title}_完整版.txt"
            with open(save_path, 'w', encoding='utf-8') as f:
                f.write(f"书名：{title}\n")
                f.write(f"作者：{author}\n")
                f.write(f"来源：{site_name}\n")
                f.write(f"下载时间：{time.strftime('%Y-%m-%d %H:%M:%S')}\n\n")
                
                for chapter in chapters:
                    f.write(f"\n{chapter['title']}\n\n")
                    f.write(f"{chapter['content']}\n")
            
            book_info = {
                'title': title,
                'author': author,
                'source': site_name,
                'path': str(save_path),
                'chapters': chapters,
                'download_time': time.strftime('%Y-%m-%d %H:%M:%S')
            }
            
            self.download_finished.emit(book_info)
            
        except Exception as e:
            self.error_occurred.emit(str(e)) 